package entities;

import entities.exceptions.BlockedTileException;
import graphics.PropertiesPanel;
import java.awt.Image;
import willispace.Log;
import willispace.WilliSpace;
import static entities.Actions.BuilderActions.*;

/**
 * Builder Class.
 * @author mateusz
 */
public class Builder extends Robot {

    private int factoriesBuilded;

    /**
     * Creates builder.
     * @param tile      Tile on which builder will be created
     * @param img       builder image
     * @param myName    name of entity
     */
    public Builder(Tile tile, Image img, String myName) {
        super(tile, img, myName);

        factoriesBuilded = 0;

        updateProperties();
        updateLocation();
        t.start();
    }

    /**
     * Updates properties of this entity
     * @see PropertiesPanel
     */
    @Override
    protected void updateProperties() {
        super.updateProperties();

        properties.put("factoriesBuilded", Integer.toString(factoriesBuilded));
    }

    /**
     * Build gas factory at specified tile
     * @param t                     Tile on which factory will be builded
     * @throws BlockedTileException If tile is blocked (e.g. by rock)
     */
    public void buildGasFactory(Tile t) throws BlockedTileException {
        buildFactory(t, Supplies.GAS);
    }

     /**
     * Build diamond factory at specified tile
     * @param t                     Tile on which factory will be builded
     * @throws BlockedTileException If tile is blocked (e.g. by rock)
     */
    public void buildDiamondFactory(Tile t) throws BlockedTileException {
        buildFactory(t, Supplies.DIAMOND);
    }

    
     /**
     * Build factory with specified supply at specified tile
     * @param t                     Tile on which factory will be builded
     * @param supply                Supply which factory will extract
     * @throws BlockedTileException If tile is blocked (e.g. by rock)
     */
    private synchronized void buildFactory(Tile t, Supplies supply) throws BlockedTileException {
        // add route to tile with new factory
        go(t);

        // create target
        Actions a;
        if (supply == Supplies.DIAMOND) {
            a = BUILD_DIAMOND_FACTORY;
        } else {
            a = BUILD_GAS_FACTORY;
        }
        addTarget(t, a);
    }

    /**
     * Decides if builder can build factory on tile t
     * @param t Tile to check
     * @return  True if tile is not blocked and is not on any route
     */
    public static boolean canBuildFactoryOnTile(Tile t){
        // jeśli pole jest zablokowane (zasób, fabryka) lub przebiega przez nie droga
        return !(t.isBlocked() && t.isOnRoute());
    }
    
    /**
     * Specified builder actions in targets
     * @param target    current Targer
     */
    @Override
    protected void action(Target target) {
        Actions action = target.action;

        if (action == BUILD_DIAMOND_FACTORY || action == BUILD_GAS_FACTORY) {
            Supplies supply;
            if (action == BUILD_DIAMOND_FACTORY) {
                supply = Supplies.DIAMOND;
            } else {
                supply = Supplies.GAS;
            }

            WilliSpace.buildFactory(target.tile, supply);
            factoriesBuilded++;
        }
    }

    /**
     * Move robot to specified tile and stop
     * @param t                     Target tile
     * @throws BlockedTileException if tile is blocked (e.g. by rock)
     */
    public void goTo(Tile t) throws BlockedTileException {
        if (t.isBlocked()) {
            throw new BlockedTileException();
        }
        
        go(t);

        // add target
        addTarget(t, STOP);
        
        // wake up this robot
        wakeUp();
    }
}
